import cv2 as cv
import numpy as np
import argparse
import random as ran
'''
思路：视频采集
      图像预处理
      背景提取
      前景分割
      图像特征描述
      最终结果
'''

cap=cv.VideoCapture('F:\\data\\vtest.avi')#打开视频，获取图片某帧

#一些基本操作
width=int(cap.get(cv.CAP_PROP_FRAME_WIDTH))#获取图片宽度
height=int(cap.get(cv.CAP_PROP_FRAME_HEIGHT))#获取图片高度
fps=cap.get(cv.CAP_PROP_FPS)#获取图片帧率
print(fps,width,height)

ap = argparse.ArgumentParser()
ap.add_argument("-v", "--video", help="path to the video file")
ap.add_argument("-a", "--min-area", type=int, default=500, help="minimum area size")
args = vars(ap.parse_args())

bsmaskMOG2=np.zeros([height,width],np.uint8)#创建一个空白视频

sub=cv.createBackgroundSubtractorMOG2()#背景提取，2可调节的参数更多



#形态学处理
xingtaixue=cv.getStructuringElement(cv.MORPH_CROSS,(3,3))#形态学处理getStructuringElement,第一个参数是结构元素，
                                                         # 一共有两种可能，cv.MORPH_CROSS和cv.MOPTH_RECT,
                                                         # 第二个参数是结构元素的大小
#判断视频捕获是否初始化成功，成功为true
while cap.isOpened():
    (flag,frame)=cap.read()
    if not flag:
        break
    cv.imshow("input video",frame)
    bsmaskMOG2=sub.apply(frame)#在创建的空白视频当中更新背景,这时候已经做出了背景提取，进行去噪就行了
    OPEND=cv.morphologyEx(bsmaskMOG2,cv.MORPH_OPEN,xingtaixue)#形态学处理：处理的对象，
                                                              # 运算（.MORPH_CLOSE，.MORPH_OPEN），结构元素
    cv.imshow('mod2',OPEND)

    image = OPEND.copy()#拷贝一个形态学处理之后的图像


    #findContours函数会返回三个值，
    # 第一个是寻找轮廓的图像，第二个是轮廓的向量，第三个是数组，需要的往往都是中间的那个
    #findContours函数中第一个参数是输入的图像，
    # 第二个参数是轮廓的检索模式：RETP_EXTERNAL只检测外轮廓，RETR_LIST检测的轮廓不建立等级关系，
    # RETR_CCOMP建立两个等级的轮廓，RETR_TREE建立一个等级树结构的轮廓
    (cnts,_)=cv.findContours(image,cv.RETR_EXTERNAL,cv.CHAIN_APPROX_SIMPLE)
    m=0
    for c in cnts:
        if cv.contourArea(c)<args["min_area"]:
            continue
        m+=1

        #输出最小包围矩形
        (x,y,w,h)=cv.boundingRect(c)#xy是矩阵左上点的坐标（一个点），wh是矩阵的宽和高
        #画出最小包围矩形
        cv.rectangle(frame,(x,y),(x+w,y+h),(ran.randint(0,225),ran.randint(0,225),ran.randint(0,225)),2)
        #第一个参数是原图，第二个参数是左上点的坐标，第三个参数是右下点的坐标，第四个参数是画线所对应的颜色
        #第五个参数是所画线的宽度
        print('target{},x:{},y:{}'.format(m,x,y))
    print("----------------------------------")
    cv.imshow("kuangkuang",frame)






    #退出
    C=cv.waitKey(40)#必须在循环内,waitkey一个给定的时间内(单位ms)等待用户按键触发;如果用户没有按下 键,则接续等待(循环)
    if C==27:
        break#OpenCv等待用户触发事件,等待时间为100ms，如果在这个时间段内, 用户按下ESC(ASCII码为27),则跳出循环,否则,则继续循环





